package com.example.shiro.common.util;

import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.exceptions.JWTDecodeException;
import com.auth0.jwt.interfaces.DecodedJWT;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;

import java.io.UnsupportedEncodingException;
import java.util.*;

/**
 * @auther 严旭平
 * @date 2020/4/24 9:54
 * @Description jwt工具类
 */
public class JwtUtil {

    private static Logger logger = LoggerFactory.getLogger(JwtUtil.class );
    /**
     * token过期时间
     */
    @Value("${ jwt.expire.date }")
    public static final long EXPIRE_TIME = 30 * 60 * 1000;


    /**
     * 私有构造方法
     */
    private JwtUtil(){}

    /**
     * 利用自身的用户名和密码生成签名token
     * @param username 用户名
     * @param secret 密码
     * @return
     */
    public static String sign( String username , String secret )  {

        /**
         * 获取过期时间
         */
        Date expirationDate = new Date( System.currentTimeMillis() + EXPIRE_TIME );

        /**
         * 封装签名信息
         */
        try {
            return JWT.create()
                    .withClaim("username" , username )
                    .withExpiresAt(expirationDate)
                    .sign( Algorithm.HMAC384( secret ) );
        } catch (UnsupportedEncodingException e) {
            logger.debug("签名生成失败");
            return null;
        }
    }

    /**
     * 获取用户名
     * @param token
     * @return
     */
    public static String getUsername(String token) {
        if( Objects.isNull( token  ) ){
            return null;
        }

        try {
            DecodedJWT jwt = JWT.decode(token);
            return jwt.getClaim("username").asString();
        } catch (JWTDecodeException e) {
            logger.debug("JWT解码异常");
            return null;
        }
    }


    /**
     * 判断token是否未过期
     * @param token
     * @return
     */
    public static Boolean isTokenExpired( String token ){
        if( Objects.isNull( token  ) ){
            return false;
        }
        DecodedJWT jwt = JWT.decode(token);
        Date expiresAt = jwt.getExpiresAt();
        if( expiresAt != null && expiresAt.before( new Date() )  ){
            logger.debug("token已经过期");
            return false;
        }
        return true;
    }

}
